package com.etc.drug.service.impl;

import cn.hutool.json.JSONUtil;
import com.etc.common.mapper.LogMapper;
import com.etc.common.utils.Result;
import com.etc.common.utils.UUIDUtil;
import com.etc.drug.entity.Drug;
import com.etc.drug.entity.OutBound;
import com.etc.drug.mapper.DrugMapper;
import com.etc.drug.mapper.PrescriptionMapper;
import com.etc.drug.service.DrugService;
import com.sun.org.apache.xpath.internal.operations.Bool;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.web.bind.annotation.RequestParam;

import javax.annotation.Resource;
import java.util.Date;
import java.util.List;

import static com.etc.common.utils.RedisConstants.*;


@Service
public class DrugServiceImpl implements DrugService {

    @Resource
    private DrugMapper drugMapper;
    @Resource
    private PrescriptionMapper prescriptionMapper;

    @Resource
    private LogMapper logMapper;
    @Resource
    private StringRedisTemplate stringRedisTemplate;

    /**
     * 根据处方Id查询药品出库信息
     */
    @Override
    public Result queryByPId(@RequestParam("prescriptionId") String prescriptionId) {
        List<OutBound> list = drugMapper.queryByPId(prescriptionId);
        return Result.ok(list);
    }

    @Override
    public Result storage(String drugId, Integer drugPack, Date drugValidity, Integer storageNum, String operatorId) {
        //对进货数量进行单位换算
        storageNum *= drugPack;
        //删除redis中的缓存
        stringRedisTemplate.delete(CACHE_DRUGNUM);
        //记录日志
        logMapper.insert(UUIDUtil.getUUID(), operatorId, "进货了" + storageNum + "个" + drugId + "药品");
        return Result.ok(drugMapper.storage(UUIDUtil.getUUID(), drugId, drugValidity, storageNum));
    }

    @Override
    public Result outbound(String prescriptionId, String drugId, Date drugValidity, Integer outboundNum, String operatorId) {
        //删除redis中的缓存
        stringRedisTemplate.delete(CACHE_DRUGNUM);
        return Result.ok(drugMapper.outbound(UUIDUtil.getUUID(), prescriptionId, drugId, drugValidity, outboundNum));
    }

    private List<Drug> RedisCache(Integer pageNum, Integer pageSize, String key) {
        //判断redis中是否有缓存
        Boolean isExist = stringRedisTemplate.hasKey(key);
        if (!isExist) {
            //没有缓存，从数据库中查询
            List<Drug> list = null;
            //如果传入的key为查询库存药品数量的key
            if (key.equals(CACHE_DRUGNUM)) {
                //是，则查询所有药品库存数量
                list = drugMapper.queryDrugNum();
            } else {
                //不是，则为查询药品类目的key,查询所有药品类目
                list = drugMapper.queryCategory();
            }
            for (Drug drug : list) {
                //转化成json
                String jsonStr = JSONUtil.toJsonStr(drug);
                //写入redis
                stringRedisTemplate.opsForList().leftPush(key, jsonStr);
            }
        }
        List<String> json = stringRedisTemplate.opsForList().range(key,
                pageSize * (pageNum - 1), pageSize * (pageNum - 1) + pageSize - 1);
        List<Drug> list = JSONUtil.toList(json.toString(), Drug.class);
        return list;
    }

    @Override
    public Result queryDrugNum(Integer pageNum, Integer pageSize) {
        List<Drug> list = RedisCache(pageNum, pageSize, CACHE_DRUGNUM);
        return Result.ok(list,(long)list.size());
    }

    @Override
    public Result retrieval(String outboundId, String operatorId) {
        //根据 医生开处方添加药品的 Id 查询药品库存数量，并返回
        Integer drugNum = drugMapper.queryByOutboundId(outboundId);
        //根据 医生开处方添加药品的 Id 查询处方Id
        String prescriptionId = drugMapper.queryPrescriptionId(outboundId);
        if (drugNum == null) {
            return Result.fail(-1, "查询药品信息失败");
        } else if (drugNum >= 0) {
            //库存充足，修改库存状态为1，表示已出库
            drugMapper.updateStatus(outboundId, 1);
            //判断病人药品是否全部取完
            if (drugMapper.count(prescriptionId) == 0) {
                //病人取完药品
                //修改处方审核为1，表示已通过，处方状态为1，已取药
                prescriptionMapper.updateStatus(prescriptionId, 1, 1);
                //删除redis，抓药人的redis缓存
                stringRedisTemplate.delete(CACHE_PRESCRIPTION + ":auditor:" + prescriptionId);
                //删除药品redis中的缓存
                stringRedisTemplate.delete(CACHE_DRUGNUM);
            }
            //记录日志
            logMapper.insert(UUIDUtil.getUUID(), operatorId, "取药成功，库存Id为：" + outboundId);
        } else {
            //库存不足，修改处方审核为1，表示通过，处方状态为0，未取药
            prescriptionMapper.updateStatus(prescriptionId, 1, 0);
            return Result.fail(-1, "库存不足");
        }
        return Result.ok(1, "取药成功");
    }

    @Override
    public Result queryCategory(Integer pageNum, Integer pageSize) {
        List<Drug> list = RedisCache(pageNum, pageSize, CACHE_CATEGORY);
        return Result.ok(list,(long)list.size());
    }

    @Override
    public Result insert(Drug drug) {
        //删除redis中的缓存
        stringRedisTemplate.delete(CACHE_CATEGORY);
        //根据药品名称和厂商判断数据库是否存在该药品
        Integer flag = drugMapper.queryByNameAndVendor(drug.getDrugName(), drug.getDrugVendor());
        if (flag > 0) {
            return Result.fail(-1, "该药品已存在");
        }
        //不存在，添加药品
        drug.setDrugId(UUIDUtil.getUUID());
        drugMapper.insert(drug);
        return Result.ok(1, "添加成功");
    }

    @Override
    public Result update(Drug drug) {
        //删除redis中的缓存
        stringRedisTemplate.delete(CACHE_CATEGORY);
        return Result.ok(drugMapper.update(drug));
    }

}
